#include "weather.h"
#include "smart_home_ui.h"
#include "calendar.h"
#include "myfont.h"
#include <time.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#include "cJSON.h"

// 天气API配置
#define API_HOST "api.k780.com"
#define API_PORT 80
#define HTTP_TIMEOUT 10  // 10秒超时
#define BUFFER_SIZE 4096
#define MAX_RESPONSE_SIZE 8192

// 获取公网IP的API配置
#define IP_GET_HOST1 "api.ipify.org"
#define IP_GET_PATH1 "/?format=text"
#define IP_GET_HOST2 "ifconfig.me"
#define IP_GET_PATH2 "/ip"
#define IP_GET_HOST3 "icanhazip.com"
#define IP_GET_PATH3 "/"
#define IP_GET_PORT 80

// 外部函数声明
extern void force_clear_screen_ghosting(void);

// 内部函数声明
static char* try_get_ip_from_service(const char* host, const char* path);
static const char* get_aqi_level_description(int aqi);

// 全局UI对象
static lv_obj_t *weather_screen = NULL;
static lv_obj_t *weather_date_label = NULL;
static lv_obj_t *weather_time_label = NULL;
static lv_timer_t *weather_time_timer = NULL;

// 天气数据显示对象
static lv_obj_t *weather_city_label = NULL;
static lv_obj_t *weather_temp_prefix_label = NULL;
static lv_obj_t *weather_temp_label = NULL;
static lv_obj_t *weather_desc_label = NULL;
static lv_obj_t *weather_humidity_label = NULL;
static lv_obj_t *weather_wind_label = NULL;
static lv_obj_t *weather_icon_img = NULL;
static lv_obj_t *weather_temp_high_label = NULL;
static lv_obj_t *weather_temp_low_label = NULL;
static lv_obj_t *weather_aqi_label = NULL;
static lv_obj_t *weather_aqi_desc_label = NULL;

// 用于防止多次清理的标志
static bool is_cleanup_in_progress = false;

// 当前天气API数据
static weather_api_data_t current_api_data = {0};

// 套接字HTTP请求函数
static char* http_get_request(const char* host, int port, const char* path) {
    int sockfd;
    struct sockaddr_in server_addr;
    struct hostent *server;
    char request[1024];
    char buffer[BUFFER_SIZE];
    char *response = NULL;
    int response_size = 0;
    int bytes_received;
    
    // 创建套接字
    sockfd = socket(AF_INET, SOCK_STREAM, 0);
    if (sockfd < 0) {
        printf("套接字创建失败\n");
        return NULL;
    }
    
    // 设置超时
    struct timeval timeout;
    timeout.tv_sec = HTTP_TIMEOUT;
    timeout.tv_usec = 0;
    setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, &timeout, sizeof(timeout));
    setsockopt(sockfd, SOL_SOCKET, SO_SNDTIMEO, &timeout, sizeof(timeout));
    
    // 获取主机信息
    server = gethostbyname(host);
    if (server == NULL) {
        printf("无法解析主机名: %s\n", host);
        close(sockfd);
        return NULL;
    }
    
    // 设置服务器地址
    memset(&server_addr, 0, sizeof(server_addr));
    server_addr.sin_family = AF_INET;
    server_addr.sin_port = htons(port);
    memcpy(&server_addr.sin_addr.s_addr, server->h_addr, server->h_length);
    
    // 连接到服务器
    if (connect(sockfd, (struct sockaddr*)&server_addr, sizeof(server_addr)) < 0) {
        printf("连接失败\n");
        close(sockfd);
        return NULL;
    }
    
    // 构造HTTP请求
    snprintf(request, sizeof(request),
        "GET %s HTTP/1.1\r\n"
        "Host: %s\r\n"
        "User-Agent: Weather-Client/1.0\r\n"
        "Connection: close\r\n"
        "\r\n", path, host);
    
    // 发送请求
    if (send(sockfd, request, strlen(request), 0) < 0) {
        printf("发送请求失败\n");
        close(sockfd);
        return NULL;
    }
    
    // 分配响应缓冲区
    response = malloc(MAX_RESPONSE_SIZE);
    if (!response) {
        printf("内存分配失败\n");
        close(sockfd);
        return NULL;
    }
    
    // 接收响应
    while ((bytes_received = recv(sockfd, buffer, BUFFER_SIZE - 1, 0)) > 0) {
        if (response_size + bytes_received >= MAX_RESPONSE_SIZE - 1) {
            break; // 防止缓冲区溢出
        }
        memcpy(response + response_size, buffer, bytes_received);
        response_size += bytes_received;
    }
    
    response[response_size] = '\0';
    close(sockfd);
    
    // 查找HTTP响应体（跳过HTTP头）
    char *body = strstr(response, "\r\n\r\n");
    if (body) {
        body += 4; // 跳过"\r\n\r\n"
        // 将响应体移到缓冲区开头
        int body_len = strlen(body);
        memmove(response, body, body_len + 1);
    }
    
    return response;
}

// 判断是否为夜间（根据温度格式判断）
static bool is_night_time(const char* temperature) {
    if(!temperature || strlen(temperature) == 0) {
        return false;  // 默认白天
    }
    
    // 使用sscanf来解析温度，更简单可靠
    int day_temp, night_temp;
    int parsed = sscanf(temperature, "%d℃/%d℃", &day_temp, &night_temp);
    
    if(parsed == 2) {
        // 如果白天和夜间温度相同，说明是夜间
        // 例如："24℃/24℃" 表示夜间，"31℃/24℃" 表示白天
        bool is_night = (day_temp == night_temp);
        return is_night;
    } else {
        return false;  // 解析失败，默认白天
    }
}

// 根据天气图标ID获取对应的图标
static const lv_img_dsc_t* get_weather_icon_by_id(const char* icon_id, bool is_night) {
    if(!icon_id || strlen(icon_id) == 0) {
        return is_night ? &n_00 : &d_00;  // 根据时间返回默认图标
    }
    
    int id = atoi(icon_id);
    
    // 根据白天/夜间选择相应的图标
    if(is_night) {
        // 夜间图标
        switch(id) {
            case 0:   return &n_00;   case 1:   return &n_01;   case 2:   return &n_02;
            case 3:   return &n_03;   case 4:   return &n_04;   case 5:   return &n_05;
            case 6:   return &n_06;   case 7:   return &n_07;   case 8:   return &n_08;
            case 9:   return &n_09;   case 10:  return &n_10;   case 11:  return &n_11;
            case 12:  return &n_12;   case 13:  return &n_13;   case 14:  return &n_14;
            case 15:  return &n_15;   case 16:  return &n_16;   case 17:  return &n_17;
            case 18:  return &n_18;   case 19:  return &n_19;   case 20:  return &n_20;
            case 21:  return &n_21;   case 22:  return &n_22;   case 23:  return &n_23;
            case 24:  return &n_24;   case 25:  return &n_25;   case 26:  return &n_26;
            case 27:  return &n_27;   case 28:  return &n_28;   case 29:  return &n_29;
            case 30:  return &n_30;   case 31:  return &n_31;   case 32:  return &n_32;
            case 33:  return &n_33;   case 49:  return &n_49;   case 53:  return &n_53;
            case 54:  return &n_54;   case 55:  return &n_55;   case 56:  return &n_56;
            case 57:  return &n_57;   case 58:  return &n_58;   case 301: return &n_301;
            case 302: return &n_302;
            default:  return &n_00;   // 默认使用夜间00号图标
        }
    } else {
        // 白天图标
        switch(id) {
            case 0:   return &d_00;   case 1:   return &d_01;   case 2:   return &d_02;
            case 3:   return &d_03;   case 4:   return &d_04;   case 5:   return &d_05;
            case 6:   return &d_06;   case 7:   return &d_07;   case 8:   return &d_08;
            case 9:   return &d_09;   case 10:  return &d_10;   case 11:  return &d_11;
            case 12:  return &d_12;   case 13:  return &d_13;   case 14:  return &d_14;
            case 15:  return &d_15;   case 16:  return &d_16;   case 17:  return &d_17;
            case 18:  return &d_18;   case 19:  return &d_19;   case 20:  return &d_20;
            case 21:  return &d_21;   case 22:  return &d_22;   case 23:  return &d_23;
            case 24:  return &d_24;   case 25:  return &d_25;   case 26:  return &d_26;
            case 27:  return &d_27;   case 28:  return &d_28;   case 29:  return &d_29;
            case 30:  return &d_30;   case 31:  return &d_31;   case 32:  return &d_32;
            case 33:  return &d_33;   case 49:  return &d_49;   case 53:  return &d_53;
            case 54:  return &d_54;   case 55:  return &d_55;   case 56:  return &d_56;
            case 57:  return &d_57;   case 58:  return &d_58;   case 301: return &d_301;
            case 302: return &d_302;
            default:  return &d_00;   // 默认使用白天00号图标
        }
    }
}

// 获取AQI空气质量等级描述
static const char* get_aqi_level_description(int aqi) {
    if (aqi <= 50) {
        return "1级 优 - 参加户外活动呼吸清新空气";
    } else if (aqi <= 100) {
        return "2级 良 - 可以正常进行室外活动";
    } else if (aqi <= 150) {
        return "3级 轻度污染 - 敏感人群减少体力消耗大的户外活动";
    } else if (aqi <= 200) {
        return "4级 中度污染 - 对敏感人群影响较大";
    } else if (aqi <= 300) {
        return "5级 重度污染 - 所有人应适当减少室外活动";
    } else {
        return "6级 严重污染 - 尽量不要留在室外";
    }
}

// 尝试从单个IP服务获取公网IP
static char* try_get_ip_from_service(const char* host, const char* path) {
    int sockfd;
    struct sockaddr_in server_addr;
    struct hostent *server;
    char request[512];
    char *response;
    char *ip_str = NULL;
    
    printf("尝试从 %s 获取IP...\n", host);
    
    // 分配响应缓冲区
    response = malloc(1024);
    if(!response) {
        printf("内存分配失败\n");
        return NULL;
    }
    
    // 创建socket
    sockfd = socket(AF_INET, SOCK_STREAM, 0);
    if(sockfd < 0) {
        printf("创建socket失败\n");
        free(response);
        return NULL;
    }
    
    // 设置超时
    struct timeval timeout;
    timeout.tv_sec = 5;  // 缩短超时时间到5秒
    timeout.tv_usec = 0;
    setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, (char *)&timeout, sizeof(timeout));
    setsockopt(sockfd, SOL_SOCKET, SO_SNDTIMEO, (char *)&timeout, sizeof(timeout));
    
    // 获取主机信息
    server = gethostbyname(host);
    if(server == NULL) {
        printf("无法解析主机: %s\n", host);
        close(sockfd);
        free(response);
        return NULL;
    }
    
    // 设置服务器地址
    memset(&server_addr, 0, sizeof(server_addr));
    server_addr.sin_family = AF_INET;
    server_addr.sin_port = htons(IP_GET_PORT);
    memcpy(&server_addr.sin_addr.s_addr, server->h_addr, server->h_length);
    
    // 连接到服务器
    if(connect(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0) {
        printf("连接 %s 失败\n", host);
        close(sockfd);
        free(response);
        return NULL;
    }
    
    // 构造HTTP请求
    snprintf(request, sizeof(request),
        "GET %s HTTP/1.1\r\n"
        "Host: %s\r\n"
        "User-Agent: Weather-Client/1.0\r\n"
        "Connection: close\r\n"
        "\r\n",
        path, host);
    
    // 发送请求
    if(send(sockfd, request, strlen(request), 0) < 0) {
        printf("发送请求到 %s 失败\n", host);
        close(sockfd);
        free(response);
        return NULL;
    }
    
    // 接收响应
    memset(response, 0, 1024);
    int total_received = 0;
    int bytes_received;
    
    while(total_received < 1023) {
        bytes_received = recv(sockfd, response + total_received, 
                             1023 - total_received, 0);
        if(bytes_received <= 0) break;
        total_received += bytes_received;
    }
    
    close(sockfd);
    
    if(total_received > 0) {
        printf("从 %s 接收到 %d 字节数据\n", host, total_received);
        
        // 查找HTTP响应体（跳过HTTP头）
        char *body_start = strstr(response, "\r\n\r\n");
        if(body_start) {
            body_start += 4; // 跳过 "\r\n\r\n"
        } else {
            // 尝试查找 \n\n 分隔符
            body_start = strstr(response, "\n\n");
            if(body_start) {
                body_start += 2; // 跳过 "\n\n"
            }
        }
        
        if(body_start && strlen(body_start) > 0) {
            // 去除末尾的换行符和空格
            char *end = body_start + strlen(body_start) - 1;
            while(end > body_start && (*end == '\n' || *end == '\r' || *end == ' ' || *end == '\t')) {
                *end = '\0';
                end--;
            }
            
            // 验证是否是有效的IP地址格式
            if(strlen(body_start) >= 7 && strlen(body_start) <= 15) {  // 最短x.x.x.x 最长xxx.xxx.xxx.xxx
                // 分配IP字符串内存
                ip_str = malloc(32);
                if(ip_str) {
                    strncpy(ip_str, body_start, 31);
                    ip_str[31] = '\0';
                    printf("从 %s 获取到IP: %s\n", host, ip_str);
                }
            } else {
                printf("从 %s 获取的数据格式不正确: %s\n", host, body_start);
            }
        }
    } else {
        printf("从 %s 未接收到数据\n", host);
    }
    
    free(response);
    return ip_str;
}

// 获取本机公网IP地址（尝试多个服务）
char* get_public_ip(void) {
    char *ip_str = NULL;
    
    printf("正在获取公网IP地址...\n");
    
    // 尝试服务1
    ip_str = try_get_ip_from_service(IP_GET_HOST1, IP_GET_PATH1);
    if(ip_str) return ip_str;
    
    // 尝试服务2
    ip_str = try_get_ip_from_service(IP_GET_HOST2, IP_GET_PATH2);
    if(ip_str) return ip_str;
    
    // 尝试服务3
    ip_str = try_get_ip_from_service(IP_GET_HOST3, IP_GET_PATH3);
    if(ip_str) return ip_str;
    
    printf("所有IP获取服务都失败了，使用备用IP地址\n");
    
    // 如果所有服务都失败，使用一个中国境内的公网IP进行测试
    // 这里使用的是百度的公共服务器IP（位于北京）
    ip_str = malloc(32);
    if(ip_str) {
        strcpy(ip_str, "220.181.38.251");  // 百度北京服务器
        printf("使用备用IP地址: %s (北京)\n", ip_str);
    }
    
    return ip_str;
}

// 获取IP地理位置信息功能已被移除，现在直接使用IP地址查询天气

// 通过IP地址获取天气数据
bool fetch_weather_by_ip(weather_api_data_t *data, const char *ip) {
    if(!data || !ip) return false;
    
    int sockfd;
    struct sockaddr_in server_addr;
    struct hostent *server;
    char request[1024];
    char *response;
    char *json_start;
    bool success = false;
    
    printf("正在获取天气数据（通过IP: %s）...\n", ip);
    
    // 初始化数据
    memset(data, 0, sizeof(weather_api_data_t));
    
    // 分配响应缓冲区
    response = malloc(MAX_RESPONSE_SIZE);
    if(!response) {
        printf("内存分配失败\n");
        return false;
    }
    
    // 创建socket
    sockfd = socket(AF_INET, SOCK_STREAM, 0);
    if(sockfd < 0) {
        printf("创建socket失败\n");
        free(response);
        return false;
    }
        
        // 设置超时
    struct timeval timeout;
    timeout.tv_sec = HTTP_TIMEOUT;
    timeout.tv_usec = 0;
    setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, (char *)&timeout, sizeof(timeout));
    setsockopt(sockfd, SOL_SOCKET, SO_SNDTIMEO, (char *)&timeout, sizeof(timeout));
    
    // 获取主机信息
    server = gethostbyname(API_HOST);
    if(server == NULL) {
        printf("无法解析主机: %s\n", API_HOST);
        close(sockfd);
        free(response);
        return false;
    }
    
    // 设置服务器地址结构
    memset(&server_addr, 0, sizeof(server_addr));
    server_addr.sin_family = AF_INET;
    server_addr.sin_port = htons(API_PORT);
    memcpy(&server_addr.sin_addr.s_addr, server->h_addr, server->h_length);
    
    // 连接服务器
    if(connect(sockfd, (struct sockaddr*)&server_addr, sizeof(server_addr)) < 0) {
        printf("连接服务器失败\n");
        close(sockfd);
        free(response);
        return false;
    }
    
    // 构造动态的API路径（使用cityIp参数）
    char api_path[512];
    snprintf(api_path, sizeof(api_path), 
        "/?app=weather.today&cityIp=%s&appkey=77125&sign=bda3123d214cc89f21df7fd82752ee14&format=json", 
        ip);
    
    // 构造HTTP请求
    snprintf(request, sizeof(request),
        "GET %s HTTP/1.1\r\n"
        "Host: %s\r\n"
        "User-Agent: Weather-Client/1.0\r\n"
        "Connection: close\r\n"
        "\r\n",
        api_path, API_HOST);
    
    // 发送请求
    if(send(sockfd, request, strlen(request), 0) < 0) {
        printf("发送请求失败\n");
        close(sockfd);
        free(response);
        return false;
    }
    
    // 接收响应
    memset(response, 0, MAX_RESPONSE_SIZE);
    int total_received = 0;
    int bytes_received;
    
    while(total_received < MAX_RESPONSE_SIZE - 1) {
        bytes_received = recv(sockfd, response + total_received, 
                             MAX_RESPONSE_SIZE - 1 - total_received, 0);
        if(bytes_received <= 0) break;
        total_received += bytes_received;
    }
    
    close(sockfd);
    
    if(total_received > 0) {
        printf("HTTP请求成功，接收到 %d 字节数据\n", total_received);
        printf("原始响应前200字符: %.200s\n", response);
        
        // 查找JSON数据开始位置（跳过HTTP头）
        json_start = strstr(response, "\r\n\r\n");
        if(json_start) {
            json_start += 4; // 跳过 "\r\n\r\n"
        } else {
            // 尝试查找 \n\n 分隔符
            json_start = strstr(response, "\n\n");
            if(json_start) {
                json_start += 2; // 跳过 "\n\n"
            }
        }
        
        if(json_start) {
            // 有时候HTTP头后面还有内容长度等信息，需要找到真正的JSON开始
            char *real_json_start = strchr(json_start, '{');
            if(real_json_start) {
                json_start = real_json_start;
            }
            
            printf("JSON响应长度: %zu\n", strlen(json_start));
            printf("完整JSON内容:\n%s\n", json_start);
            printf("================================\n");
            
            // 解析JSON
            cJSON *json = cJSON_Parse(json_start);
            if(json) {
                cJSON *success_item = cJSON_GetObjectItem(json, "success");
                if(success_item && success_item->type == cJSON_String) {
                    if(strcmp(success_item->valuestring, "1") == 0) {
                        // 解析成功，提取result对象
                        cJSON *result = cJSON_GetObjectItem(json, "result");
                        if(result) {
                            cJSON *item;
                            
                            item = cJSON_GetObjectItem(result, "days");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->days, item->valuestring, sizeof(data->days) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "week");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->week, item->valuestring, sizeof(data->week) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "citynm");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->citynm, item->valuestring, sizeof(data->citynm) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "temperature");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->temperature, item->valuestring, sizeof(data->temperature) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "temperature_curr");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->temperature_curr, item->valuestring, sizeof(data->temperature_curr) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "humidity");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->humidity, item->valuestring, sizeof(data->humidity) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "weather");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->weather, item->valuestring, sizeof(data->weather) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "weather_curr");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->weather_curr, item->valuestring, sizeof(data->weather_curr) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "wind");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->wind, item->valuestring, sizeof(data->wind) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "winp");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->winp, item->valuestring, sizeof(data->winp) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "temp_high");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->temp_high, item->valuestring, sizeof(data->temp_high) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "temp_low");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->temp_low, item->valuestring, sizeof(data->temp_low) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "aqi");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->aqi, item->valuestring, sizeof(data->aqi) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "weather_iconid");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->weather_iconid, item->valuestring, sizeof(data->weather_iconid) - 1);
                            }
                            
                            item = cJSON_GetObjectItem(result, "weather_icon");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->weather_icon, item->valuestring, sizeof(data->weather_icon) - 1);
                            }
                            
                            data->is_valid = true;
                            success = true;
                            printf("天气数据解析成功: %s, %s, %s\n", 
                                   data->citynm, data->weather_curr, data->temperature_curr);
                            printf("天气图标信息:\n");
                            printf("  - 图标ID: %s\n", data->weather_iconid);
                            printf("  - 图标URL: %s\n", data->weather_icon);
                        }
                    } else {
                        printf("API返回错误，success=%s\n", success_item->valuestring);
                    }
                }
                cJSON_Delete(json);
            } else {
                printf("JSON解析失败\n");
            }
        } else {
            printf("未找到JSON数据\n");
        }
    } else {
        printf("未接收到数据\n");
    }
    
    free(response);
    
    if(!success) {
        printf("天气数据获取失败，使用默认显示\n");
    }
    
    return success;
}

// 获取天气数据（原函数，使用weaId参数）
bool fetch_weather_data(weather_api_data_t *data, const char *weaid) {
    if(!data || !weaid) return false;
    
    int sockfd;
    struct sockaddr_in server_addr;
    struct hostent *server;
    char request[1024];
    char *response;
    char *json_start;
    bool success = false;
    
        printf("正在获取天气数据...\n");
    
    // 分配响应缓冲区
    response = malloc(MAX_RESPONSE_SIZE);
    if(!response) {
        printf("内存分配失败\n");
        return false;
    }
    
    // 创建socket
    sockfd = socket(AF_INET, SOCK_STREAM, 0);
    if(sockfd < 0) {
        printf("创建socket失败\n");
        free(response);
        return false;
    }
    
    // 设置超时
    struct timeval timeout;
    timeout.tv_sec = HTTP_TIMEOUT;
    timeout.tv_usec = 0;
    setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, &timeout, sizeof(timeout));
    setsockopt(sockfd, SOL_SOCKET, SO_SNDTIMEO, &timeout, sizeof(timeout));
    
    // 获取服务器地址
    server = gethostbyname(API_HOST);
    if(server == NULL) {
        printf("无法解析主机名: %s\n", API_HOST);
        close(sockfd);
        free(response);
        return false;
    }
    
    // 设置服务器地址结构
    memset(&server_addr, 0, sizeof(server_addr));
    server_addr.sin_family = AF_INET;
    server_addr.sin_port = htons(API_PORT);
    memcpy(&server_addr.sin_addr.s_addr, server->h_addr, server->h_length);
    
    // 连接服务器
    if(connect(sockfd, (struct sockaddr*)&server_addr, sizeof(server_addr)) < 0) {
        printf("连接服务器失败\n");
        close(sockfd);
        free(response);
        return false;
    }
    
    // 构造动态的API路径
    char api_path[512];
    snprintf(api_path, sizeof(api_path), 
        "/?app=weather.today&weaId=%s&appkey=77125&sign=bda3123d214cc89f21df7fd82752ee14&format=json", 
        weaid);
    
    // 构造HTTP请求
    snprintf(request, sizeof(request),
        "GET %s HTTP/1.1\r\n"
        "Host: %s\r\n"
        "User-Agent: Weather-Client/1.0\r\n"
        "Connection: close\r\n"
        "\r\n",
        api_path, API_HOST);
    
    // 发送请求
    if(send(sockfd, request, strlen(request), 0) < 0) {
        printf("发送请求失败\n");
        close(sockfd);
        free(response);
        return false;
    }
    
    // 接收响应
    memset(response, 0, MAX_RESPONSE_SIZE);
    int total_received = 0;
    int bytes_received;
    
    while(total_received < MAX_RESPONSE_SIZE - 1) {
        bytes_received = recv(sockfd, response + total_received, 
                             MAX_RESPONSE_SIZE - 1 - total_received, 0);
        if(bytes_received <= 0) break;
        total_received += bytes_received;
    }
    
    close(sockfd);
    
    if(total_received > 0) {
        printf("HTTP请求成功，接收到 %d 字节数据\n", total_received);
        printf("原始响应前200字符: %.200s\n", response);
        
        // 查找JSON数据开始位置（跳过HTTP头）
        json_start = strstr(response, "\r\n\r\n");
        if(json_start) {
            json_start += 4; // 跳过 "\r\n\r\n"
        } else {
            // 尝试查找 \n\n 分隔符
            json_start = strstr(response, "\n\n");
            if(json_start) {
                json_start += 2; // 跳过 "\n\n"
            }
        }
        
        if(json_start) {
            // 有时候HTTP头后面还有内容长度等信息，需要找到真正的JSON开始
            char *real_json_start = strchr(json_start, '{');
            if(real_json_start) {
                json_start = real_json_start;
            }
            
            printf("JSON响应长度: %zu\n", strlen(json_start));
            printf("完整JSON内容:\n%s\n", json_start);
            printf("================================\n");
            
                // 解析JSON
            cJSON *json = cJSON_Parse(json_start);
                if(json) {
                    cJSON *success_item = cJSON_GetObjectItem(json, "success");
                if(success_item && success_item->type == cJSON_String) {
                        if(strcmp(success_item->valuestring, "1") == 0) {
                            // 解析成功，提取result对象
                            cJSON *result = cJSON_GetObjectItem(json, "result");
                            if(result) {
                                // 清空数据结构
                                memset(data, 0, sizeof(weather_api_data_t));
                                
                                // 提取各个字段
                                cJSON *item;
                                
                                item = cJSON_GetObjectItem(result, "days");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->days, item->valuestring, sizeof(data->days) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "week");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->week, item->valuestring, sizeof(data->week) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "citynm");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->citynm, item->valuestring, sizeof(data->citynm) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "temperature");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->temperature, item->valuestring, sizeof(data->temperature) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "temperature_curr");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->temperature_curr, item->valuestring, sizeof(data->temperature_curr) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "humidity");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->humidity, item->valuestring, sizeof(data->humidity) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "weather");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->weather, item->valuestring, sizeof(data->weather) - 1);
                                }
                            
                            item = cJSON_GetObjectItem(result, "weather_curr");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->weather_curr, item->valuestring, sizeof(data->weather_curr) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "wind");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->wind, item->valuestring, sizeof(data->wind) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "winp");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->winp, item->valuestring, sizeof(data->winp) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "temp_high");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->temp_high, item->valuestring, sizeof(data->temp_high) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "temp_low");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->temp_low, item->valuestring, sizeof(data->temp_low) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "aqi");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->aqi, item->valuestring, sizeof(data->aqi) - 1);
                                }
                                
                                item = cJSON_GetObjectItem(result, "weather_iconid");
                            if(item && item->type == cJSON_String) {
                                    strncpy(data->weather_iconid, item->valuestring, sizeof(data->weather_iconid) - 1);
                                }
                            
                            item = cJSON_GetObjectItem(result, "weather_icon");
                            if(item && item->type == cJSON_String) {
                                strncpy(data->weather_icon, item->valuestring, sizeof(data->weather_icon) - 1);
                                }
                                
                                data->is_valid = true;
                                success = true;
                                printf("天气数据解析成功: %s, %s, %s\n", 
                                   data->citynm, data->weather_curr, data->temperature_curr);
                            printf("天气图标信息:\n");
                            printf("  - 图标ID: %s\n", data->weather_iconid);
                            printf("  - 图标URL: %s\n", data->weather_icon);
                            }
                        } else {
                            printf("API返回错误，success=%s\n", success_item->valuestring);
                        }
                    }
                    cJSON_Delete(json);
                } else {
                    printf("JSON解析失败\n");
                }
        } else {
            printf("未找到JSON数据\n");
            }
        } else {
        printf("HTTP请求失败，未接收到数据\n");
    }
    
    free(response);
    return success;
}

// 更新天气显示
void update_weather_display(const weather_api_data_t *data) {
    if(!data || !data->is_valid) return;
    
    // 更新城市名
    if(weather_city_label && strlen(data->citynm) > 0) {
        char city_text[128];  // 增大缓冲区大小
        snprintf(city_text, sizeof(city_text), "%s", data->citynm);
        lv_label_set_text(weather_city_label, city_text);
    }
    
    // 更新当前温度
    if(weather_temp_label && strlen(data->temperature_curr) > 0) {
        char temp_text[32];
        // 提取温度数字部分并添加度数符号
        if(strstr(data->temperature_curr, "℃")) {
            // 如果包含℃，替换为°C
            char temp_num[16];
            strncpy(temp_num, data->temperature_curr, sizeof(temp_num) - 1);
            temp_num[sizeof(temp_num) - 1] = '\0';
            char *celsius_pos = strstr(temp_num, "℃");
            if(celsius_pos) {
                *celsius_pos = '\0';  // 截断℃部分
            }
            snprintf(temp_text, sizeof(temp_text), "%s°C", temp_num);
        } else {
            // 如果没有单位，直接添加°C
            snprintf(temp_text, sizeof(temp_text), "%s°C", data->temperature_curr);
        }
        lv_label_set_text(weather_temp_label, temp_text);
    }
    
    // 更新天气描述
    if(weather_desc_label && strlen(data->weather_curr) > 0) {
        char weather_desc_text[128];
        snprintf(weather_desc_text, sizeof(weather_desc_text), "天气: %s", data->weather_curr);
        lv_label_set_text(weather_desc_label, weather_desc_text);
    }
    
    // 更新湿度
    if(weather_humidity_label && strlen(data->humidity) > 0) {
        char humidity_text[64];
        snprintf(humidity_text, sizeof(humidity_text), "湿度: %s", data->humidity);
        lv_label_set_text(weather_humidity_label, humidity_text);
    }
    
    // 更新风向风力
    if(weather_wind_label && strlen(data->wind) > 0 && strlen(data->winp) > 0) {
        char wind_text[128];
        snprintf(wind_text, sizeof(wind_text), "风向: %s %s", data->wind, data->winp);
        lv_label_set_text(weather_wind_label, wind_text);
    }
    
    // 更新天气图标
    if(weather_icon_img && strlen(data->weather_iconid) > 0) {
        // 根据温度格式判断是否为夜间
        bool is_night = is_night_time(data->temperature);
        const lv_img_dsc_t *icon = get_weather_icon_by_id(data->weather_iconid, is_night);
        lv_img_set_src(weather_icon_img, icon);
    }
    
    // 更新最高温度（只更新数值部分，使用°C符号）
    if(weather_temp_high_label && strlen(data->temp_high) > 0) {
        char temp_high_text[32];
        snprintf(temp_high_text, sizeof(temp_high_text), "%s°C", data->temp_high);
        lv_label_set_text(weather_temp_high_label, temp_high_text);
    }
    
    // 更新最低温度（只更新数值部分，使用°C符号）
    if(weather_temp_low_label && strlen(data->temp_low) > 0) {
        char temp_low_text[32];
        snprintf(temp_low_text, sizeof(temp_low_text), "%s°C", data->temp_low);
        lv_label_set_text(weather_temp_low_label, temp_low_text);
    }
    
    // 更新AQI
    if(weather_aqi_label && strlen(data->aqi) > 0) {
        char aqi_text[64];
        snprintf(aqi_text, sizeof(aqi_text), "AQI: %s", data->aqi);
        lv_label_set_text(weather_aqi_label, aqi_text);
        
        // 更新AQI等级说明
        if(weather_aqi_desc_label) {
            int aqi_value = atoi(data->aqi);
            const char* aqi_desc = get_aqi_level_description(aqi_value);
            lv_label_set_text(weather_aqi_desc_label, aqi_desc);
        }
    }
    
    printf("天气显示更新完成\n");
}

// 旧的模拟天气数据结构体和变量已移除，现在使用API数据

/**
 * @brief 天气页面时间更新任务
 * @param timer 定时器对象
 */
static void weather_update_time_task(lv_timer_t *timer) {
    // 如果正在清理，直接返回
    if(is_cleanup_in_progress) {
        return;
    }
    
    // 检查对象是否还有效
    if(!weather_date_label || !weather_time_label || !weather_screen) {
        return;
    }
    
    static char last_date_str[32] = "";
    static char last_time_str[16] = "";
    static bool first_run = true;
    
    // 获取当前时间
    time_t now;
    struct tm *local_time;
    char date_str[32];
    char time_str[16];
    
    time(&now);
    local_time = localtime(&now);
    
    // 格式化日期和时间，为天气页面添加秒数显示
    strftime(date_str, sizeof(date_str), "%Y年%m月%d日", local_time);  // 移除星期显示，避免中文字体问题
    strftime(time_str, sizeof(time_str), "%H:%M:%S", local_time);  // 添加秒数显示
    
    // 首次运行或日期发生变化时更新日期
    if(first_run || strcmp(date_str, last_date_str) != 0) {
        if(weather_date_label && !is_cleanup_in_progress) {
            lv_label_set_text(weather_date_label, date_str);
            strcpy(last_date_str, date_str);
        }
    }
    
    // 首次运行或时间发生变化时更新时间
    if(first_run || strcmp(time_str, last_time_str) != 0) {
        if(weather_time_label && !is_cleanup_in_progress) {
            lv_label_set_text(weather_time_label, time_str);
            strcpy(last_time_str, time_str);
        }
    }
    
    // 标记首次运行完成
    if(first_run) {
        first_run = false;
    }
}

/**
 * @brief 重置天气页面时间更新任务的静态变量
 * @note 在重新创建天气界面时调用，确保时间能正确显示
 */
static void reset_weather_time_task(void) {
    // 通过调用时间更新函数并传入NULL来重置静态变量
    // 这样在下次创建天气界面时会强制更新时间
}

/**
 * @brief 返回按钮点击事件回调函数
 * @param e 事件对象
 */
static void back_btn_event_cb(lv_event_t *e) {
    if(lv_event_get_code(e) != LV_EVENT_CLICKED) return;
    
    // 防止重复点击
    if(is_cleanup_in_progress) {
        return;
    }
    
    // 设置清理标志
    is_cleanup_in_progress = true;
    
    // 立即停止定时器
    if(weather_time_timer) {
        lv_timer_del(weather_time_timer);
        weather_time_timer = NULL;
    }
    
    // 清理全局对象指针
    weather_date_label = NULL;
    weather_time_label = NULL;
    weather_screen = NULL;
    
    // 使用安全的返回方式，避免在事件回调中直接删除当前屏幕
    return_to_smart_home_ui();
    
    // 重置清理标志
    is_cleanup_in_progress = false;
}

// 延迟切换到日历界面的回调函数
static void delayed_calendar_switch_cb(lv_timer_t *timer) {
    cleanup_weather_ui();
    create_calendar_screen();
    lv_timer_del(timer);  // 删除定时器
}

/**
 * @brief 滑动手势处理函数
 * @param e 事件对象
 */
static void weather_gesture_event_cb(lv_event_t *e) {
    lv_event_code_t code = lv_event_get_code(e);
    
    if (code == LV_EVENT_GESTURE) {
        lv_dir_t dir = lv_indev_get_gesture_dir(lv_indev_get_act());
        if (dir == LV_DIR_LEFT) {
            // 右滑手势，延迟进入老黄历页面
            printf("检测到右滑手势，进入老黄历页面\n");
            lv_timer_create(delayed_calendar_switch_cb, 5, NULL);
        }
    }
}

/**
 * @brief 创建天气页面
 * @note 创建单屏幕展示所有天气信息的界面
 */
void create_weather_screen(void) {
    // 清理之前的界面
    cleanup_weather_ui();
    
    // 强制清除屏幕残影
    force_clear_screen_ghosting();
    

    
    // 创建屏幕，使用与首页类似的主题背景
    weather_screen = lv_obj_create(NULL);
    lv_obj_set_style_bg_color(weather_screen, lv_color_hex(0x2c3e50), LV_PART_MAIN);
    lv_obj_set_style_bg_opa(weather_screen, LV_OPA_COVER, LV_PART_MAIN);
    lv_obj_clear_flag(weather_screen, LV_OBJ_FLAG_SCROLLABLE);
    
    // 添加滑动手势支持
    lv_obj_add_event_cb(weather_screen, weather_gesture_event_cb, LV_EVENT_GESTURE, NULL);
    
    // 使用安全的屏幕切换方式，避免段错误
    // 使用快速淡入动画，提供更流畅的切换体验
    lv_scr_load_anim(weather_screen, LV_SCR_LOAD_ANIM_FADE_ON, 100, 0, false);
    
    // 让LVGL自动处理旧屏幕清理，避免手动删除导致的内存问题
    
    // ==================== 顶部控制和信息区域 ====================
    // 返回按钮（左上角，与设备界面一致）
    lv_obj_t *btn_back = lv_btn_create(weather_screen);
    lv_obj_set_size(btn_back, 72, 40);
    lv_obj_align(btn_back, LV_ALIGN_TOP_LEFT, 12, 10);
    lv_obj_add_event_cb(btn_back, back_btn_event_cb, LV_EVENT_CLICKED, NULL);
    lv_obj_set_style_bg_color(btn_back, lv_color_hex(0xe74c3c), LV_PART_MAIN);
    lv_obj_set_style_border_width(btn_back, 0, LV_PART_MAIN);
    lv_obj_set_style_radius(btn_back, 8, LV_PART_MAIN);
    lv_obj_set_style_shadow_width(btn_back, 0, LV_PART_MAIN);
    
    lv_obj_t *back_label = lv_label_create(btn_back);
    lv_label_set_text(back_label, LV_SYMBOL_LEFT " 返回");
    lv_obj_set_style_text_font(back_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(back_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_center(back_label);
    
    // 标题
    lv_obj_t *title_label = lv_label_create(weather_screen);
    lv_label_set_text(title_label, "今日天气");
    lv_obj_set_style_text_font(title_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(title_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_align(title_label, LV_ALIGN_TOP_MID, 0, 15);
    
    // 时间显示（右上角，贴着屏幕右侧）
    weather_date_label = lv_label_create(weather_screen);
    lv_obj_set_style_text_font(weather_date_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(weather_date_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_align(weather_date_label, LV_ALIGN_TOP_RIGHT, -5, 10);  // 进一步贴近右侧边缘
    
    weather_time_label = lv_label_create(weather_screen);
    lv_obj_set_style_text_font(weather_time_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(weather_time_label, lv_color_hex(0xC0C0C0), 0);
    // 使用与日期相同的右对齐基准，确保右侧完全对齐
    lv_obj_align(weather_time_label, LV_ALIGN_TOP_RIGHT, -5, 40);  // 与日期使用相同偏移，确保右侧完全对齐
    
    // 立即设置当前时间，避免显示"加载中..."
    time_t now;
    struct tm *local_time;
    char date_str[32];
    char time_str[16];
    
    time(&now);
    local_time = localtime(&now);
    strftime(date_str, sizeof(date_str), "%Y年%m月%d日", local_time);
    strftime(time_str, sizeof(time_str), "%H:%M:%S", local_time);  // 添加秒数显示
    
    lv_label_set_text(weather_date_label, date_str);
    lv_label_set_text(weather_time_label, time_str);
    
    // ==================== 主要天气信息区域 ====================
    // 创建主容器
    lv_obj_t *main_container = lv_obj_create(weather_screen);
    lv_obj_set_size(main_container, 760, 280);
    lv_obj_align(main_container, LV_ALIGN_TOP_MID, 0, 70);
    lv_obj_set_style_bg_color(main_container, lv_color_hex(0x34495e), LV_PART_MAIN);
    lv_obj_set_style_border_width(main_container, 0, LV_PART_MAIN);
    lv_obj_set_style_radius(main_container, 15, LV_PART_MAIN);
    lv_obj_set_style_pad_all(main_container, 15, LV_PART_MAIN);
    lv_obj_set_style_shadow_width(main_container, 0, LV_PART_MAIN);
    lv_obj_clear_flag(main_container, LV_OBJ_FLAG_SCROLLABLE);
    
    // 左上角城市名称
    weather_city_label = lv_label_create(main_container);
    lv_label_set_text(weather_city_label, "加载中...");
    lv_obj_set_style_text_font(weather_city_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(weather_city_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_align(weather_city_label, LV_ALIGN_TOP_LEFT, 0, 0);
    
    // 天气图标（左侧）
    weather_icon_img = lv_img_create(main_container);
    lv_img_set_src(weather_icon_img, &d_00);
    lv_obj_set_size(weather_icon_img, 180, 180);  // 稍微小一点
    lv_obj_align(weather_icon_img, LV_ALIGN_LEFT_MID, 20, 15);
    lv_obj_add_flag(weather_icon_img, LV_OBJ_FLAG_OVERFLOW_VISIBLE);
    lv_img_set_size_mode(weather_icon_img, LV_IMG_SIZE_MODE_REAL);
    
    // 图标右侧信息区域
    lv_obj_t *info_container = lv_obj_create(main_container);
    lv_obj_set_size(info_container, 480, 200);
    lv_obj_align_to(info_container, weather_icon_img, LV_ALIGN_OUT_RIGHT_MID, 30, 0);
    lv_obj_set_style_bg_opa(info_container, LV_OPA_TRANSP, LV_PART_MAIN);
    lv_obj_set_style_border_opa(info_container, LV_OPA_TRANSP, LV_PART_MAIN);
    lv_obj_set_style_pad_all(info_container, 0, LV_PART_MAIN);
    lv_obj_clear_flag(info_container, LV_OBJ_FLAG_SCROLLABLE);
    
    // 天气描述信息（放在最上方）
    weather_desc_label = lv_label_create(info_container);
    lv_label_set_text(weather_desc_label, "天气: 加载中...");
    lv_obj_set_style_text_font(weather_desc_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(weather_desc_label, lv_color_hex(0x3498db), 0);  // 使用蓝色突出显示天气描述
    lv_obj_align(weather_desc_label, LV_ALIGN_TOP_LEFT, 0, 0);
    
    // 温度前缀标签（中文）
    weather_temp_prefix_label = lv_label_create(info_container);
    lv_label_set_text(weather_temp_prefix_label, "温度: ");
    lv_obj_set_style_text_font(weather_temp_prefix_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(weather_temp_prefix_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_set_style_transform_zoom(weather_temp_prefix_label, 350, 0);
    lv_obj_align_to(weather_temp_prefix_label, weather_desc_label, LV_ALIGN_OUT_BOTTOM_LEFT, 0, 15);
    
    // 当前温度数值（英文字体支持°符号）
    weather_temp_label = lv_label_create(info_container);
    lv_label_set_text(weather_temp_label, "Loading...");
    lv_obj_set_style_text_font(weather_temp_label, &lv_font_montserrat_20, 0);  // 使用LVGL字体支持°符号
    lv_obj_set_style_text_color(weather_temp_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_set_style_transform_zoom(weather_temp_label, 350, 0);  // 更大的温度显示
    lv_obj_align_to(weather_temp_label, weather_temp_prefix_label, LV_ALIGN_OUT_RIGHT_MID, 10, 0);
    
    // 湿度信息
    weather_humidity_label = lv_label_create(info_container);
    lv_label_set_text(weather_humidity_label, "湿度: 加载中...");
    lv_obj_set_style_text_font(weather_humidity_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(weather_humidity_label, lv_color_hex(0xC0C0C0), 0);
    lv_obj_align_to(weather_humidity_label, weather_temp_prefix_label, LV_ALIGN_OUT_BOTTOM_LEFT, 0, 15);
    
    // 日期和星期
    lv_obj_t *date_week_label = lv_label_create(info_container);
    time(&now);
    local_time = localtime(&now);
    char date_week_str[64];
    strftime(date_week_str, sizeof(date_week_str), "%m月%d日 %A", local_time);
    lv_label_set_text(date_week_label, date_week_str);
    lv_obj_set_style_text_font(date_week_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(date_week_label, lv_color_hex(0xC0C0C0), 0);
    lv_obj_align_to(date_week_label, weather_humidity_label, LV_ALIGN_OUT_BOTTOM_LEFT, 0, 15);
    
    // 风向风速信息
    weather_wind_label = lv_label_create(info_container);
    lv_label_set_text(weather_wind_label, "风向: 加载中...");
    lv_obj_set_style_text_font(weather_wind_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(weather_wind_label, lv_color_hex(0xC0C0C0), 0);
    lv_obj_align_to(weather_wind_label, date_week_label, LV_ALIGN_OUT_BOTTOM_LEFT, 0, 15);
    
    // ==================== 详细信息区域 ====================
    // 创建详细信息容器，使用与首页类似的主题色彩，调整位置适应新布局
    lv_obj_t *detail_container = lv_obj_create(weather_screen);
    lv_obj_set_size(detail_container, 760, 180);  // 稍微增加高度
    lv_obj_align(detail_container, LV_ALIGN_TOP_MID, 0, 370);  // 调整位置适应新布局
    lv_obj_set_style_bg_color(detail_container, lv_color_hex(0x34495e), LV_PART_MAIN);
    lv_obj_set_style_border_width(detail_container, 0, LV_PART_MAIN);
    lv_obj_set_style_radius(detail_container, 15, LV_PART_MAIN);
    lv_obj_set_style_pad_all(detail_container, 15, LV_PART_MAIN);
    lv_obj_set_style_shadow_width(detail_container, 0, LV_PART_MAIN);
    // 禁用详细信息容器的滚动功能
    lv_obj_clear_flag(detail_container, LV_OBJ_FLAG_SCROLLABLE);
    
    // 最高温度 - 创建复合标签容器
    lv_obj_t *temp_high_container = lv_obj_create(detail_container);
    lv_obj_set_size(temp_high_container, 200, 30);
    lv_obj_align(temp_high_container, LV_ALIGN_TOP_LEFT, 0, 0);
    lv_obj_set_style_bg_opa(temp_high_container, LV_OPA_TRANSP, LV_PART_MAIN);
    lv_obj_set_style_border_opa(temp_high_container, LV_OPA_TRANSP, LV_PART_MAIN);
    lv_obj_set_style_pad_all(temp_high_container, 0, LV_PART_MAIN);
    lv_obj_clear_flag(temp_high_container, LV_OBJ_FLAG_SCROLLABLE);
    
    // 中文标签部分
    lv_obj_t *temp_high_cn_label = lv_label_create(temp_high_container);
    lv_label_set_text(temp_high_cn_label, "最高温度: ");
    lv_obj_set_style_text_font(temp_high_cn_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(temp_high_cn_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_align(temp_high_cn_label, LV_ALIGN_LEFT_MID, 0, 0);
    
    // 温度数值部分
    lv_obj_t *temp_high_label = lv_label_create(temp_high_container);
    lv_label_set_text(temp_high_label, "Loading...");
    lv_obj_set_style_text_font(temp_high_label, &lv_font_montserrat_20, 0);  // 使用支持°符号的字体
    lv_obj_set_style_text_color(temp_high_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_align_to(temp_high_label, temp_high_cn_label, LV_ALIGN_OUT_RIGHT_MID, 0, 0);
    
    // 最低温度 - 创建复合标签容器
    lv_obj_t *temp_low_container = lv_obj_create(detail_container);
    lv_obj_set_size(temp_low_container, 200, 30);
    lv_obj_align(temp_low_container, LV_ALIGN_TOP_RIGHT, 0, 0);
    lv_obj_set_style_bg_opa(temp_low_container, LV_OPA_TRANSP, LV_PART_MAIN);
    lv_obj_set_style_border_opa(temp_low_container, LV_OPA_TRANSP, LV_PART_MAIN);
    lv_obj_set_style_pad_all(temp_low_container, 0, LV_PART_MAIN);
    lv_obj_clear_flag(temp_low_container, LV_OBJ_FLAG_SCROLLABLE);
    
    // 中文标签部分
    lv_obj_t *temp_low_cn_label = lv_label_create(temp_low_container);
    lv_label_set_text(temp_low_cn_label, "最低温度: ");
    lv_obj_set_style_text_font(temp_low_cn_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(temp_low_cn_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_align(temp_low_cn_label, LV_ALIGN_LEFT_MID, 0, 0);
    
    // 温度数值部分
    lv_obj_t *temp_low_label = lv_label_create(temp_low_container);
    lv_label_set_text(temp_low_label, "Loading...");
    lv_obj_set_style_text_font(temp_low_label, &lv_font_montserrat_20, 0);  // 使用支持°符号的字体
    lv_obj_set_style_text_color(temp_low_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_align_to(temp_low_label, temp_low_cn_label, LV_ALIGN_OUT_RIGHT_MID, 0, 0);
    
    // AQI空气质量
    lv_obj_t *aqi_label = lv_label_create(detail_container);
    lv_label_set_text(aqi_label, "AQI: 加载中...");
    lv_obj_set_style_text_font(aqi_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(aqi_label, lv_color_hex(0xFFFFFF), 0);
    lv_obj_align_to(aqi_label, temp_high_label, LV_ALIGN_OUT_BOTTOM_LEFT, 0, 20);
    
    // AQI等级说明
    lv_obj_t *aqi_desc_label = lv_label_create(detail_container);
    lv_label_set_text(aqi_desc_label, "空气质量等级说明");
    lv_obj_set_style_text_font(aqi_desc_label, &lv_font_source_han_sans_bold_20, 0);
    lv_obj_set_style_text_color(aqi_desc_label, lv_color_hex(0xC0C0C0), 0);
    lv_obj_align_to(aqi_desc_label, aqi_label, LV_ALIGN_OUT_BOTTOM_LEFT, 0, 15);
    
    // 存储UI对象供更新使用
    weather_temp_high_label = temp_high_label;
    weather_temp_low_label = temp_low_label;
    weather_aqi_label = aqi_label;
    weather_aqi_desc_label = aqi_desc_label;
    
    // ==================== 底部区域 ====================
    // 移除不需要的状态信息文本，保持简洁的界面
    
    // 启动时间更新定时器（每秒更新一次）
    weather_time_timer = lv_timer_create(weather_update_time_task, 1000, NULL);
    // 定时器创建成功后立即执行一次，确保时间显示正确
    if(weather_time_timer) {
        // 不需要立即调用，因为我们已经在上面设置了初始时间
        // weather_update_time_task(weather_time_timer);
    }
    
    // 获取并显示真实天气数据
    // 直接使用IP地址查询天气
    char *public_ip = get_public_ip();
    bool weather_success = false;
    
    if(public_ip) {
        printf("获取到公网IP: %s，直接查询天气\n", public_ip);
        
        // 使用IP地址直接查询天气
        if(fetch_weather_by_ip(&current_api_data, public_ip)) {
            update_weather_display(&current_api_data);
            printf("通过IP地址获取天气数据成功并已更新显示\n");
            weather_success = true;
        }
        
        free(public_ip);  // 释放IP字符串内存
    }
    
    if(!weather_success) {
        printf("IP获取失败，尝试使用手动IP测试...\n");
        
        // 测试：尝试使用一个示例IP地址
        const char* test_ip = "113.66.97.208";  // 默认ip
        printf("测试使用IP: %s 查询天气\n", test_ip);
        
        if(fetch_weather_by_ip(&current_api_data, test_ip)) {
            update_weather_display(&current_api_data);
            printf("使用测试IP获取天气数据成功\n");
            weather_success = true;
        }
    }
    
    if(!weather_success) {
        printf("所有方法都失败，使用默认广州天气\n");
        // 使用默认的北京天气
        if(fetch_weather_data(&current_api_data, "165")) {
            update_weather_display(&current_api_data);
            printf("使用默认位置获取天气数据成功\n");
        } else {
            printf("天气数据获取失败，使用默认显示\n");
        }
    }
    
    // 最终刷新确保界面完全显示
    lv_obj_invalidate(weather_screen);
    lv_refr_now(lv_disp_get_default());
}

/**
 * @brief 清理天气页面资源
 * @note 安全地释放天气页面相关的UI对象和定时器
 */
void cleanup_weather_ui(void) {
    // 防止重复清理
    if(is_cleanup_in_progress) {
        return;
    }
    
    // 先停止定时器
    if(weather_time_timer) {
        lv_timer_del(weather_time_timer);
        weather_time_timer = NULL;
    }
    
    // 清理全局对象指针（注意：不要删除weather_screen，让lv_scr_load自动处理）
    weather_date_label = NULL;
    weather_time_label = NULL;
    weather_city_label = NULL;
    weather_temp_prefix_label = NULL;
    weather_temp_label = NULL;
    weather_desc_label = NULL;
    weather_humidity_label = NULL;
    weather_wind_label = NULL;
    weather_icon_img = NULL;
    weather_temp_high_label = NULL;
    weather_temp_low_label = NULL;
    weather_aqi_label = NULL;
    weather_aqi_desc_label = NULL;
    weather_screen = NULL;
}